package com.hxzy.controller.system;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.hxzy.common.annotation.Log;
import com.hxzy.common.annotation.RepeatSubmit;
import com.hxzy.common.constant.UserConstants;
import com.hxzy.common.core.controller.BaseController;
import com.hxzy.common.core.domain.AjaxResult;
import com.hxzy.common.core.domain.R;
import com.hxzy.common.core.domain.entity.SysRole;
import com.hxzy.common.core.domain.model.LoginUser;
import com.hxzy.common.enums.AckCode;
import com.hxzy.common.enums.BusinessType;
import com.hxzy.common.exception.ServiceException;
import com.hxzy.common.utils.StringUtils;
import com.hxzy.common.utils.poi.ExcelUtil;
import com.hxzy.system.domain.dto.SysRoleSearchDTO;
import com.hxzy.system.domain.dto.ValueChangeDTO;
import com.hxzy.system.domain.dto.ValueExistsDTO;
import com.hxzy.system.service.ISysMenuService;
import com.hxzy.system.service.ISysRoleService;
import com.hxzy.system.service.ISysUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

@RestController
@RequestMapping(value = "/api")
@Api(tags = "角色API")
public class SysRoleController  extends BaseController {

    @Autowired
    private ISysRoleService sysRoleService;

    @Autowired
    private ISysMenuService sysMenuService;

    @Autowired
    private ISysUserService sysUserService;



    @PreAuthorize(value = "@hxzy.hasPermi('system:role:list')")
    @ApiOperation(value = "分页查询")
    @GetMapping(value = "/system/role/list")
    public R search(SysRoleSearchDTO sysRoleSearchDTO){
        IPage<SysRole> page=this.sysRoleService.search(sysRoleSearchDTO);
        return super.pageVO(page);
    }

    @RepeatSubmit
    @PreAuthorize(value = "@hxzy.hasPermi('system:role:add')")
    @Log(title = "角色管理", businessType = BusinessType.INSERT)
    @PostMapping(value = "/system/role")
    @ApiOperation(value = "新增角色")
    public R addData(@RequestBody @Valid SysRole sysRole){
        // 检查角色名是否唯一
        if(this.sysRoleService.checkRoleNameUnique(new ValueExistsDTO(null,sysRole.getRoleName()))>0){
            throw new ServiceException(AckCode.EXISTS_VALUE.getMsg());
        }

        //检查角色权限是否唯一
        if(this.sysRoleService.checkRoleKeyUnique(new ValueExistsDTO(null,sysRole.getRoleName()))>0){
            throw new ServiceException(AckCode.EXISTS_VALUE.getMsg());
        }

        boolean success= this.sysRoleService.addData(sysRole);
        return  super.toAjax(success);
    }


    @PreAuthorize(value = "@hxzy.hasPermi('system:role:edit')")
    @Log(title = "角色管理", businessType = BusinessType.UPDATE)
    @PutMapping(value = "/system/role")
    @ApiOperation(value = "修改角色")
    public R updateData(@RequestBody @Valid SysRole sysRole){
        // 检查角色名是否唯一
        if(this.sysRoleService.checkRoleNameUnique(new ValueExistsDTO(sysRole.getRoleId(),sysRole.getRoleName()))>0){
            throw new ServiceException(AckCode.EXISTS_VALUE.getMsg());
        }

        //检查角色权限是否唯一
        if(this.sysRoleService.checkRoleKeyUnique(new ValueExistsDTO(sysRole.getRoleId(),sysRole.getRoleName()))>0){
            throw new ServiceException(AckCode.EXISTS_VALUE.getMsg());
        }

        boolean success= this.sysRoleService.updateData(sysRole);

        // 是否及进更新redis缓存
        if(!super.isAdmin()){
            LoginUser loginUser = getLoginUser();
            //查询用户拥有的角色和菜单权限
            Set<String> roleSet=this.sysRoleService.selectRolePermissionByUserId(loginUser.getUserId());
            //判断是不是管理员
            boolean isSuper=roleSet.contains(UserConstants.SUPER_MAN_NAME);
            //查询用户的角色拥有的菜单权限
            Set<String> menuSet=new HashSet<>();
            if(isSuper){
                menuSet.add("*:*:*");
            }else{
                menuSet=this.sysMenuService.selectMenuPermsByUserId(loginUser.getUserId());
            }

            loginUser.setPermissions(menuSet);
            loginUser.setUser(this.sysUserService.selectUserByUserName(loginUser.getUser().getUserName()));
            //写入到redis中去
            this.sysUserService.refreshToken(loginUser);
        }

        return  super.toAjax(success);
    }




    @ApiOperation(value = "角色名称是否存在")
    @GetMapping(value = "/system/role/name/exists")
    public R checkRoleNameUnique(@Valid ValueExistsDTO valueExistsDTO){
        R  r=R.ok();
       int count=this.sysRoleService.checkRoleNameUnique(valueExistsDTO);
        if(count>0){
            r.setData(AckCode.EXISTS_VALUE.msg);
        }
        return r;
    }

    @ApiOperation(value = "权限标识是否存在")
    @GetMapping(value = "/system/role/key/exists")
    public R checkRoleKeyUnique(@Valid ValueExistsDTO valueExistsDTO){
        R  r=R.ok();
        int count=this.sysRoleService.checkRoleKeyUnique(valueExistsDTO);
        if(count>0){
            r.setData(AckCode.EXISTS_VALUE.msg);
        }
        return r;
    }

    /**
     * 根据角色编号获取详细信息
     */
    @PreAuthorize(value = "@hxzy.hasPermi('system:role:query')")
    @ApiOperation(value = "根据主键查询数据")
    @GetMapping(value = "/system/role/{roleId}")
    public AjaxResult getInfo(@PathVariable Long roleId) {
        return AjaxResult.success(this.sysRoleService.selectRoleById(roleId));
    }


    @PreAuthorize("@hxzy.hasPermi('system:role:export')")
    @PostMapping("/system/role/export")
    public void export(HttpServletResponse response,SysRoleSearchDTO sysRoleSearchDTO)
    {
        List<SysRole> list = this.sysRoleService.searchExport(sysRoleSearchDTO);
        ExcelUtil<SysRole> util = new ExcelUtil<SysRole>(SysRole.class);
        util.exportExcel(response, list, "角色数据");
    }

    /**
     * 状态修改
     */
    @PreAuthorize("@ss.hasPermi('system:role:edit')")
    @Log(title = "角色管理", businessType = BusinessType.UPDATE)
    @PutMapping("/system/role/changeStatus")
    public R changeStatus(@RequestBody @Valid ValueChangeDTO valueChangeDTO) {
      //如果是超级管理员id=1的时候，不允许操作的
        if(valueChangeDTO.getId().intValue()==1){
            return R.build(AckCode.ADMIN_VALUE_NOT_CHANGE);
        }
       SysRole  sysRole=new SysRole();
       sysRole.setRoleId(valueChangeDTO.getId());
       sysRole.setStatus(valueChangeDTO.getValue());
       boolean  result = this.sysRoleService.updateById(sysRole);
        return  super.toAjax(result);
    }

    /**
     * 删除，把状态更改为 del_flag2
     */
    @PreAuthorize("@hxzy.hasPermi('system:role:remove')")
    @Log(title = "角色管理", businessType = BusinessType.DELETE)
    @DeleteMapping(value="/system/role/{roleId}")
    public R delete( @PathVariable(value = "roleId") Long[] roleId) {
        //如果是超级管理员id=1的时候，不允许操作的
        if(StringUtils.isNull(roleId)){
            return R.build(AckCode.SYSTEM_PARAM_FAIL);
        }

        // 如果有管理员id=1不允许删除
        if(Arrays.stream(roleId).filter( p-> p.intValue()==1).count()>0){
            return R.build(AckCode.ADMIN_VALUE_NOT_CHANGE);
        }


        // 如果role被  sys_user_role  或者  sys_role_menu 使用了，就不允许删除了

         boolean  result = this.sysRoleService.deleteById(roleId);
        return  super.toAjax(result);
    }


}
